package com.fnzn.entranceGuard.service.impl;

import com.baomidou.mybatisplus.mapper.EntityWrapper;
import com.baomidou.mybatisplus.mapper.Wrapper;
import com.baomidou.mybatisplus.plugins.Page;
import com.baomidou.mybatisplus.service.impl.ServiceImpl;
import com.fnzn.entranceGuard.bean.UnitHouseBean;
import com.fnzn.entranceGuard.constant.GuardConstant;
import com.fnzn.entranceGuard.entity.GuardDevice;
import com.fnzn.entranceGuard.entity.GuardIcDevice;
import com.fnzn.entranceGuard.entity.GuardIcInfo;
import com.fnzn.entranceGuard.mapper.GuardDeviceMapper;
import com.fnzn.entranceGuard.mapper.GuardIcDeviceMapper;
import com.fnzn.entranceGuard.mapper.GuardIcInfoMapper;
import com.fnzn.entranceGuard.mapper.GuardRoleDeviceMapper;
import com.fnzn.entranceGuard.rest.guard.UsrUtil;
import com.fnzn.entranceGuard.rest.usrCloud.UsrApi;
import com.fnzn.entranceGuard.service.IGuardIcInfoService;
import com.fnzn.entranceGuard.util.QRGenerate;
import com.fnzn.entranceGuard.vo.GuardDeviceVo;
import com.fnzn.entranceGuard.vo.GuardRole;
import com.github.pig.common.constant.CommonConstant;
import com.github.pig.common.util.ResponseUtil;
import org.apache.commons.lang3.StringUtils;
import org.apache.ibatis.jdbc.Null;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.thymeleaf.util.ListUtils;

import java.util.*;

/**
 * <p>
 * IC信息管理 服务实现类
 * </p>
 *
 * @author JokerGao
 * @since 2018-06-25
 */
@Service
public class GuardIcInfoServiceImpl extends ServiceImpl<GuardIcInfoMapper, GuardIcInfo> implements IGuardIcInfoService {

    @Autowired
    private GuardIcInfoMapper guardIcInfoMapper;
    @Autowired
    private GuardRoleDeviceMapper roleMapper;
    @Autowired
    private GuardIcDeviceMapper guardIcDeviceMapper;
    @Autowired
    private GuardDeviceMapper guardDeviceMapper;



    @Override
    public Page getIcInfoById(Page<GuardIcInfo> page, String id) {
        List<GuardIcInfo> list = guardIcInfoMapper.getIcInfoByDeviceId(page,id);
        page.setRecords(list);
        return page;
    }

    @Override
    public Page selectByUserId(Page<GuardIcInfo> page, String userId) {
        List<GuardIcInfo> list = guardIcInfoMapper.selectByUserId(page,userId);
        page.setRecords(list);
        return page;
    }
    /**
     * 获取用户所在小区的CODE
     * @param userId
     * @return
     */
    @Override
    public String selectCodeByUserId(String userId) {
        List<Integer> list = guardIcInfoMapper.selectCodeByUserId(userId);
        return getCom16(list);
    }

    @Override
    public Page selectByHouseOwnerId(Page<GuardIcInfo> page, String houseOwnerId) {
        List<GuardIcInfo> list = guardIcInfoMapper.selectByHouseOwnerId(page,houseOwnerId);
        page.setRecords(list);
        return page;
    }
    /**
     * 获取业主所在小区的CODE
     * @param houseOwnerId
     * @return
     */
    @Override
    public String selectCodeByHouseOwnerId(String houseOwnerId) {
        List<Integer> list = guardIcInfoMapper.selectCodeByHouseOwnerId(houseOwnerId);
        return getCom16(list);
    }
    String getCom16(List<Integer> list){
        StringBuilder sb = new StringBuilder();
        for(Integer code: list){
            Integer first = code / 100;
            Integer second = code % 100;
            if (first < 10) {
                sb.append("0" + first);
            } else {
                sb.append(first);
            }
            if (second < 10) {
                sb.append("0" + second);
            } else {
                sb.append(second);
            }
        }

        return QRGenerate.parse16Byte2Str(QRGenerate.parseStr2HexByte(sb.toString()));
    }


    /**
     * 通过业主ID添加并插入设备
     * @param guardIcInfo
     * @return
     */
    @Override
    @Transactional(rollbackFor = Exception.class)
    public ResponseUtil addByHouseOwnerId(GuardIcInfo guardIcInfo) {
        ResponseUtil responseUtil = new ResponseUtil();
        try{
            List<GuardIcInfo> selectByIcId = guardIcInfoMapper.selectByIcId(guardIcInfo.getIcId());
            if(!ListUtils.isEmpty(selectByIcId)) {
                if(StringUtils.isNotBlank(selectByIcId.get(0).getUserId())) {
                    responseUtil.setStatus(ResponseUtil.ERROR);
                    responseUtil.setMsg("IC卡已存在于用户" + selectByIcId.get(0).getUserName() + "中，添加失败");
                } else if(StringUtils.isNotBlank(selectByIcId.get(0).getHouseOwnerId())) {
                    responseUtil.setStatus(ResponseUtil.ERROR);
                    responseUtil.setMsg("IC卡已存在于业主" + selectByIcId.get(0).getHouseOwnerName() + "中，添加失败");
                } else {
                    responseUtil.setStatus(ResponseUtil.ERROR);
                    responseUtil.setMsg("IC卡已存在，添加失败");
                }
                return responseUtil;
            }
            //todo 判断用户IC数量，最多5张
            List<GuardIcInfo> IcInfos = guardIcInfoMapper.selectIcByUserId(guardIcInfo.getIcId());
            if (IcInfos.size() > 5) {
                responseUtil.setStatus(ResponseUtil.ERROR);
                responseUtil.setMsg("添加失败，IC卡数量已达上限");
                return responseUtil;
            }
            super.insert(guardIcInfo);
            String icInfoId = guardIcInfo.getId();

            List<GuardRole> list = roleMapper.getDeviceIdsByHouseOwnerId(guardIcInfo.getHouseOwnerId());
            if(list != null) {
                StringBuffer deviceIds = new StringBuffer();
                for (GuardRole role : list) {
                    if (StringUtils.isNotBlank(role.getDeviceIds())) {
                        deviceIds.append(role.getDeviceIds());
                        deviceIds.append(",");
                    }
                }
                //对设备ID去重
                String[] dIds;//去重后的设备ID
                if (deviceIds.length() > 0) {
                    dIds = deviceIds.substring(0, deviceIds.length() - 1).split(",");
                    Arrays.sort(dIds);
                    Set<String> prodCodeSet = new HashSet<>();
                    prodCodeSet.addAll(Arrays.asList(dIds));
                    dIds = prodCodeSet.toArray(new String[]{});
                } else {
                    responseUtil.setStatus(ResponseUtil.ERROR);
                    responseUtil.setMsg("未关联设备");
                    return responseUtil;
                }
                String deviceId;//关联主键
                String deviceNumber;//设备号
                String type;//设备类型
                for (int i = 0; i < dIds.length; i++) {
                    deviceId = dIds[i];
                    if(deviceId!=null) {
                        GuardIcDevice guardIcDevice = new GuardIcDevice();
                        guardIcDevice.setIcInfoId(icInfoId);
                        guardIcDevice.setDeviceId(Integer.valueOf(deviceId));
                        guardIcDevice.setStatus(GuardConstant.SYNC);
                        guardIcDeviceMapper.insert(guardIcDevice);

                        GuardDevice guardDevice = guardDeviceMapper.selectById(deviceId);
                        deviceNumber = guardDevice.getDeviceId();
                        type = guardDevice.getType();

                        //先查看设备在不在线
                        if (UsrApi.getDevice(deviceNumber)) {
                            List<GuardIcInfo> guardIcInfoList = new ArrayList<>();
                            guardIcInfoList.add(guardIcInfo);
                            boolean flag = UsrUtil.addOrDelIcToDev(guardIcInfoList, deviceNumber, GuardConstant.TYPE_ADD, type, null);
                            if(flag) {
                                responseUtil.setStatus(ResponseUtil.SUCCESS);
                                responseUtil.setMsg("保存IC信息成功，插入设备中");
                            }else {
                                responseUtil.setStatus(ResponseUtil.ERROR);
                                responseUtil.setMsg("保存IC信息成功，插入设备出错");
                            }
                        } else{
                            responseUtil.setStatus(ResponseUtil.ERROR);
                            responseUtil.setMsg("保存IC信息成功，因设备不在线插入设备失败");
                        }
                    }
                }
            }else {
                responseUtil.setStatus(ResponseUtil.ERROR);
                responseUtil.setMsg("保存成功，未关联设备");
            }
        }catch (Exception e){
            e.printStackTrace();
            responseUtil.setStatus(ResponseUtil.ERROR);
            responseUtil.setMsg("添加失败");
        }
        return responseUtil;
    }

    /**
     * 通过用户ID添加并插入设备
     * @param guardIcInfo
     * @return
     */
    @Override
    @Transactional(rollbackFor = Exception.class)
    public ResponseUtil addByUserId(GuardIcInfo guardIcInfo) {
        ResponseUtil responseUtil = new ResponseUtil();
        try{
            List<GuardIcInfo> selectByIcId = guardIcInfoMapper.selectByIcId(guardIcInfo.getIcId());
            if(!ListUtils.isEmpty(selectByIcId)) {
                if(StringUtils.isNotBlank(selectByIcId.get(0).getUserId())) {
                    responseUtil.setStatus(ResponseUtil.ERROR);
                    responseUtil.setMsg("IC卡已存在于用户" + selectByIcId.get(0).getUserName() + "中，添加失败");
                } else if(StringUtils.isNotBlank(selectByIcId.get(0).getHouseOwnerId())) {
                    responseUtil.setStatus(ResponseUtil.ERROR);
                    responseUtil.setMsg("IC卡已存在于业主" + selectByIcId.get(0).getHouseOwnerName() + "中，添加失败");
                } else {
                    responseUtil.setStatus(ResponseUtil.ERROR);
                    responseUtil.setMsg("IC卡已存在，添加失败");
                }
                return responseUtil;
            }
            //todo 判断此业主房屋下所有IC数量，最多20张
            List<GuardIcInfo> IcInfos = guardIcInfoMapper.selectIcByHouseOwnerId(guardIcInfo.getHouseOwnerId());
            if (IcInfos.size() > 20) {
                responseUtil.setStatus(ResponseUtil.ERROR);
                responseUtil.setMsg("添加失败，IC卡数量已达上限");
                return responseUtil;
            }

            super.insert(guardIcInfo);
            String icInfoId = guardIcInfo.getId();

            List<GuardRole> list = roleMapper.getDeviceIdsByUserId(guardIcInfo.getUserId());
            if(list != null) {
                StringBuffer deviceIds = new StringBuffer();
                for (GuardRole role : list) {
                    if (StringUtils.isNotBlank(role.getDeviceIds())) {
                        deviceIds.append(role.getDeviceIds());
                        deviceIds.append(",");
                    }
                }
                //对设备ID去重
                String[] dIds;//去重后的设备ID
                if (deviceIds.length() > 0) {
                    dIds = deviceIds.substring(0, deviceIds.length() - 1).split(",");
                    Arrays.sort(dIds);
                    Set<String> prodCodeSet = new HashSet<>();
                    prodCodeSet.addAll(Arrays.asList(dIds));
                    dIds = prodCodeSet.toArray(new String[]{});
                } else {
                    responseUtil.setStatus(ResponseUtil.ERROR);
                    responseUtil.setMsg("未关联设备");
                    return responseUtil;
                }
                String deviceId;//关联主键
                String deviceNumber;//设备号
                String type;//设备类型(门禁：0；梯控：1)
                for (int i = 0; i < dIds.length; i++) {
                    deviceId = dIds[i];
                    if(deviceId!=null) {
                        GuardIcDevice guardIcDevice = new GuardIcDevice();
                        guardIcDevice.setIcInfoId(icInfoId);
                        guardIcDevice.setDeviceId(Integer.valueOf(deviceId));
                        guardIcDevice.setStatus(GuardConstant.SYNC);
                        guardIcDeviceMapper.insert(guardIcDevice);

                        GuardDevice guardDevice = guardDeviceMapper.selectById(deviceId);
                        deviceNumber = guardDevice.getDeviceId();
                        type = guardDevice.getType();

                        //先查看设备在不在线
                        if (UsrApi.getDevice(deviceNumber)) {
                            List<GuardIcInfo> guardIcInfoList = new ArrayList<>();
                            guardIcInfoList.add(guardIcInfo);
                            boolean flag = UsrUtil.addOrDelIcToDev(guardIcInfoList, deviceNumber, GuardConstant.TYPE_ADD, type, "Admin");
                            if(flag) {
                                responseUtil.setStatus(ResponseUtil.SUCCESS);
                                responseUtil.setMsg("保存IC信息成功，插入设备成功");
                            }else {
                                responseUtil.setStatus(ResponseUtil.ERROR);
                                responseUtil.setMsg("保存IC信息成功，插入设备出错");
                            }
                        } else{
                            responseUtil.setStatus(ResponseUtil.ERROR);
                            responseUtil.setMsg("保存IC信息成功，因设备不在线插入设备失败");
                        }
                    }
                }
            }else{
                responseUtil.setStatus(ResponseUtil.ERROR);
                responseUtil.setMsg("保存IC信息成功,未关联设备");
            }
        }catch (Exception e){
            e.printStackTrace();
            responseUtil.setStatus(ResponseUtil.ERROR);
            responseUtil.setMsg("添加失败");
        }
        return responseUtil;
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public ResponseUtil deleteIcInfoById(GuardIcInfo guardIcInfo) {
        ResponseUtil responseUtil = new ResponseUtil();
        try{
            String status = guardIcInfo.getStatus();//IC设备关联表状态
            String icInfoId = guardIcInfo.getId();//IcInfo表主键ID
            Integer deviceId = guardIcInfo.getDeviceId();//设备表主键ID
            String deviceNumber = guardIcInfo.getDeviceNumber();//设备号
            if(status != null && status.equals(GuardConstant.SYNC)) {//状态为同步中的，直接删除
                EntityWrapper<GuardIcDevice> entityWrapper = new EntityWrapper<>();
                entityWrapper.eq("ic_info_id",icInfoId);
                entityWrapper.eq("device_id",deviceId);
                entityWrapper.eq("status",status);
                //关联表删除
                guardIcDeviceMapper.delete(entityWrapper);
                List<GuardIcDevice> guardIcDeviceList = guardIcDeviceMapper.selectByGuardIcInfoId(icInfoId);
                if (ListUtils.isEmpty(guardIcDeviceList)) {
                    guardIcInfo.setUpdateTime(new Date());
                    guardIcInfo.setDelFlag(CommonConstant.STATUS_DEL);
                    //IC信息表删除
                    guardIcInfoMapper.updateById(guardIcInfo);
                }

                responseUtil.setStatus(ResponseUtil.SUCCESS);
                responseUtil.setMsg("删除成功");
            } else {
                super.updateById(guardIcInfo);
                //修改状态为删除中
                guardIcDeviceMapper.updateStatusTo3ByIcInfoIdAndDeviceId(icInfoId, deviceId);
                if(deviceNumber != null && !"".equals(deviceNumber)) {
                    //先查看设备在不在线
                    if (UsrApi.getDevice(deviceNumber)) {
                        List<GuardIcInfo> guardIcInfoList = new ArrayList<>();
                        guardIcInfoList.add(guardIcInfo);
                        boolean flag = UsrUtil.addOrDelIcToDev(guardIcInfoList, deviceNumber, GuardConstant.TYPE_DEL, "0", null);
                        if(flag) {
                            responseUtil.setStatus(ResponseUtil.SUCCESS);
                            responseUtil.setMsg("删除成功");
                        }else {
                            responseUtil.setStatus(ResponseUtil.ERROR);
                            responseUtil.setMsg("设备中删除失败");
                        }
                    } else{
                        responseUtil.setStatus(ResponseUtil.SUCCESS);
                        responseUtil.setMsg("删除失败，设备不在线");
                    }
                } else {
                    responseUtil.setStatus(ResponseUtil.ERROR);
                    responseUtil.setMsg("删除失败，设备为空");
                }
            }
        }catch (Exception e){
            e.printStackTrace();
            responseUtil.setStatus(ResponseUtil.ERROR);
            responseUtil.setMsg("删除失败");
        }
        return responseUtil;
    }

    public static void main(String[] args) {
        System.out.println();
    }

}
